
GM.Name = "Chimera Hunt";
GM.Author = "Aska";
GM.Email = "N/A";
GM.Website = "N/A";
GM.TeamBased = false;

GM.STATE_WAITING = 1;
GM.STATE_COUNTDOWN = 2;
GM.STATE_PLAYING = 3;
GM.STATE_END = 4;
GM.STATE_STARTING = 5;

GM.TEAM_CHIMERA = 1;
GM.TEAM_PIGMASKS = 2;
GM.TEAM_DEADPIGS = 3;

team.SetUp(GM.TEAM_CHIMERA, "Ultimate Chimera", Color(230, 30, 110, 255));
team.SetUp(GM.TEAM_PIGMASKS, "Pigmasks", Color(250, 200, 200, 255));
team.SetUp(GM.TEAM_DEADPIGS, "Dead Pigmasks", Color(248, 168, 168, 255));


//GM.ShowSplash = false; //toggles whether or not to show the splash screen on initial spawn
GM.RoundEndTime = 10; //how long to wait after a round has finished before starting another
GM.NumPlayers = 3; //number of players required for a game to start
GM.StartDelay = 5; //time in seconds before the game starts once enough players have joined
GM.RoundTimer = 1; //time in minutes a chimera has to kill the last few pigs
GM.MinForRoundTimer = 5; //number of players that must be on the server before the gamemode will use the round timer
GM.KillTimeAdd = 20; //time in seconds to add to the countdown timer when the UC kills a pig
GM.KillTimeAddNotice = .8; //time in seconds for the kill time add notice to flash before fading away

GM.RagFlyAmount = 25000; //amount that ragdolls fly when bit
GM.BtnPressDis = .42; //distance around the chimera player to press the button
GM.BtnPressDistance = 140; //distance away from the button before you can press it

GM.XHairAlpha = 25; //transparency of the pig's crosshair

GM.plySpeed = 175; //speed at which players move
GM.plySprintSpeed = 425; //speed at which players move while sprinting
GM.plyCrouchSpeed = .25; //speed at which players move while crouching
GM.plyScaredSpeed = 250; //speed at which players move while scared
GM.plySprintCooldown = 6; //how long before a player can sprint again once they've depleted sprint completely
GM.plySprintRegenRate = .00125; //rate per second at which player's sprint regens
GM.plySprintDegenRate = .0068; //rate per second at which player's sprint degens

GM.SnortTime = {4.5, 9}; //time (random between min and max) in seconds between pig snorts

GM.UCSpeed = 125; //speed at which the ultimate chimera player moves
GM.UCSprintSpeed = 300; //speed at which the ultimate chimera player moves when they sprint
GM.UCSprintRegenRate = .00175; //rate per second at which the ultimate chimera player's sprint regens
GM.UCSprintDegenRate = .00285; //rate per second at which the ultimate chimera player's sprint degens

GM.UCCamDistance = 150; //how far back the thirdperson camera sits for the ultimate chimera player
GM.UCBiteTime = .76; //how long it takes to finish biting
GM.UCRoarTime = 2.525; //how long it takes to finish roaring
GM.UCRoarDelay = 12; //how long in between roars
GM.UCRoarDistance = 450; //how close piggies must be to get scared when chimera player roars
GM.UCRoarMin = 4; //minimum amount of time one can be scared when the chimera roars at them
GM.UCRoarMax = 8; //maximum amount of time one can be scared when the chimera roars at them

GM.UCTextTime = 9; //time in seconds that the help text stays on screen
GM.UCHelpText = "Your goal is to kill all the Pigmasks.\nUse your roar to scare them off if you get surrounded."; //text to show the chimera how to play
GM.PigHelpText = "Don't get bit.\nGet behind the Ultimate Chimera and press your \"Use\" key to turn him off!"; //text to show the pigs how to play
GM.DeathNoticeTime = 6; //time in seconds a kill icon will stay on screen
GM.PigsOnRow = 5; //number of pigs per vertical row in the scoreboard before starting a new one
GM.PigWiggleVelocity = 32; //how fast the piggy wiggle goes when talking on mic
GM.PlayerNameDistance = 600; //how far away a spectator must be to see player names

GM.plyHullSizeMin = Vector(-16, -16, 0);
GM.plyHullSizeMax = Vector(16, 16, 55);
GM.plyHullSizeMaxD = Vector(16, 16, 40);
GM.plyViewOffset = 48;
GM.plyViewOffsetD = 40;
GM.UCHullSizeMin = Vector(-25, -25, 0);
GM.UCHullSizeMax = Vector(25, 25, 72);
GM.UCViewOffset = 68;

GM.PancakePlayer = Vector(1, 1, 1);
GM.PancakeChimera = Vector(1, 1, 1);
GM.PlayerMdl = ("models/player/kleiner.mdl");
GM.ChimeraMdl = ("models/player/kleiner.mdl");

function GM:Initialize()

	self.BaseClass.Initialize(self);
	self:SetState(self.STATE_WAITING);
	
end

function GM:GetState() //ex. returns 3 if state equals GM.STATE_PLAYING
	return GetGlobalInt("UCGamemodeState", self.STATE_WAITING);
end

function GM:SetState(state) //ex. GM:SetState(GM.STATE_COUNTDOWN)
	SetGlobalInt("UCGamemodeState", state);
end


function GM:KeyPress(ply, key)

	if (key == IN_SPEED && self:CanPlayerSprint(ply)) then //sprint time
		ply.UCSprinting = true;
		ply.SprintRegen = false;
		ply.PigSnort = (CurTime() + .5);
		if (SERVER) then
			if (ply:GetSprint() > 0 && ply:IsOnGround()) then
				ply:DestroySprintTimer();
			end
		end
	end
	
	if (SERVER) then
	
		if ((key == IN_ATTACK || key == IN_ATTACK2)) then
		
			if (!ply:Alive()) then
				if (self:GetState() == self.STATE_PLAYING) then
					if (!ply.Speccing) then
						local chimera = self:GetChimera();
						ply.Speccing = true;
						ply.SpecN = 0;
						ply:SetNWEntity("UCSpec", chimera);
						ply:SpectateEntity(chimera);
						ply:Spectate(OBS_MODE_CHASE);
					else
						if (key == IN_ATTACK) then //+1
							if (ply.SpecN == #ply:ExcludeMeInTable()) then //last player in list
								ply.SpecN = 1; //back to first player
							else
								ply.SpecN = (ply.SpecN + 1);
							end
						else //-1
							if (ply.SpecN == 1) then //last player in list
								ply.SpecN = #ply:ExcludeMeInTable(); //back to first player
							else
								ply.SpecN = (ply.SpecN - 1);
							end
						end
						ply:SpecNextPerson();
					end
				end
			else
				if (!ply:GetNWBool("IsChimera") && ValidEntity(ply.PigMask) && key == IN_ATTACK2 && ply:IsOnGround() && !ply:GetNWBool("Taunting", false)) then
				
					ply:SetNWBool("Taunting", true);
					ply.PigMask:SetCycle(0);
					ply:SetRenderMode(RENDERMODE_NONE);
					
					local ang = ply:EyeAngles();
					ang.p = 0;
					ply:SetEyeAngles(ang);
					
					ply:Lock();
					
					local num = 1.7;
					if (ply:GetNWInt("PigRank") == 4) then
						num = 3;
						ply.PigMask:SetPlaybackRate(1);
					end
					
					timer.Create(tostring(ply) .. "TauntTimer", num, 1, function()
						if (ValidEntity(ply)) then
							ply:SetNWBool("Taunting", false);
							ply:SetRenderMode(RENDERMODE_NORMAL);
							ply:UnLock();
						end
					end);
					
				end
			end
			
		end
		
		if ((key == IN_ATTACK || key == IN_USE) && !ply:IsChimera() && ply:Alive()) then
			if (ply:CanPressButton()) then
				self:GetChimera():EmitSound("chimerahunt/chimera/button.wav");
				
				local atch = self:GetChimera().Chimera:LookupAttachment("Button");
				atch = self:GetChimera().Chimera:GetAttachment(atch);
				
				local pos = atch.Pos;
				local effectdata = EffectData();
				effectdata:SetStart(pos);
				effectdata:SetOrigin(pos);
				effectdata:SetScale(2);
				util.Effect("Sparks", effectdata); //this isnt working  ._.
				
				GAMEMODE:SendKillNotice(ply, self:GetChimera(), "pig");
				
				if (ply:GetNWInt("PigRank") < 4) then
					ply.ShouldRank = (ply:GetNWInt("PigRank") + 1);
				end
				
				self:GetChimera():Kill();
			end
		end
		
		if (key == IN_JUMP) then
			if (ply:Alive()) then
				if (ply:IsOnGround()) then
					local ent = ply;
					if (ValidEntity(ply.PigMask)) then
						ent = ply.PigMask;
					end
					if (ValidEntity(ply.Chimera)) then
						ent = ply.Chimera;
					end
					ent:SetCycle(0);
					if (ply:GetNWBool("IsChimera") && ply:KeyDown(IN_SPEED)) then
						local num = (ply:GetNWInt("UCSprint") - .25)
						if (num < 0) then
							if (SERVER) then
								local vel = ply:GetVelocity();
								vel.z = 0;
								vel = (vel * .5);
								ply:SetLocalVelocity(vel);
							end
						end
						ply:SetNWInt("UCSprint", math.Clamp(num, 0, 1));
					end
				end
			else
				ply:AdvanceSpecMode();
			end
		end
		
	else
		if ((key == IN_ATTACK || key == IN_USE) && !ply:GetNWBool("IsChimera") && ply:Alive()) then
			ply.XHairAlpha = 200;
		end
	end
	
end


function GM:GetChimera()
	
	local ply = nil;
	for k, v in ipairs(player.GetAll()) do
		if (v:GetNWBool("IsChimera")) then
			ply = v;
		end
	end
	
	return ply;
	
end


function GM:CanPlayerSprint(ply)
	local b = false;
	if (!ply:GetNWBool("IsChimera") && ply:Alive() && !ply:Crouching() && ply:GetNWInt("UCSprint") > .25 && ply:IsOnGround()) then
		b = true;
	end
	return b;
end


function GM:PlayerFootstep(ply, pos, foot, sound, volume, rf) 
	if(CLIENT && (ply:GetNWBool("IsChimera") || !ply:Alive())) then
		return true;
	end
end
